package ecustom.finance.bean;

import ecustom.clients.k3client.K3WebApiClient;
import ecustom.clients.k3client.entities.ERPPPayableReq;
import ecustom.clients.k3client.entities.ERPPPayableReq.FEntityDetail;
import ecustom.clients.k3client.entities.ERPPPayableReq.FsubHeadFinc;
import ecustom.clients.k3client.entities.ERPPPayableReq.FsubHeadSuppiler;
import ecustom.clients.util.JsonUtil;
import ecustom.common.CustomMap;
import ecustom.common.conn.DB;
import ecustom.common.servicelog.bean.ServiceLogBean;
import ecustom.common.util.CustomUtil;
import ecustom.finance.actions.FYLFKAction;
import weaver.file.Prop;
import weaver.soa.workflow.request.DetailTable;
import weaver.soa.workflow.request.Property;
import weaver.soa.workflow.request.RequestInfo;
import weaver.soa.workflow.request.Row;

import java.sql.SQLException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
* @author 作者:Gcc
* @createDate 创建时间：Aug 24, 2023 2:40:44 PM
*/
public class PushPayableBean extends FYLFKAction{
	
	public Map<String, Object> handlERPData(RequestInfo requestInfo, Property[] mainFields) throws Exception {
		Map<String, Object> payableMap = pushPayable(requestInfo, mainFields);	// 下推应付单
		ServiceLogBean logBean = new ServiceLogBean("FYLFKAction", "ecustom.finance.actions.FYLFKAction-费用类付款-下推修改费用应付单数据",  "K3Cloud", "", System.currentTimeMillis());
		String formid = Prop.getPropValue("ecustom", "k3.yfd.formid");
		ERPPPayableReq req = updatePushPayable(requestInfo, mainFields, payableMap);
		Map<String, Object> erpResult = K3WebApiClient.saveData(logBean, req, formid);
		return erpResult;
	}
	
	/**
	 * 下推创建应付单
	 * @param requestInfo
	 * @param mainFields
	 * @return 0：失败；1：成功
	 * @throws Exception
	 */
	public Map<String, Object> pushPayable(RequestInfo requestInfo, Property[] mainFields) throws Exception {
		Integer pushPayableFID = super.getMainInteger(mainFields, "PushPayableFID");	// 下推应付单内码
		String PushPayableNumber = super.getMainString(mainFields, "PushPayableNumber");	// 下推应付单编码
		if(CustomUtil.isNotBlank(pushPayableFID) && CustomUtil.isNotBlank(PushPayableNumber) ) {	// 判断不为空的情况，直接返回成功
			Map<String, Object> resultMap = new HashMap<String, Object>();
			resultMap.put("FID", pushPayableFID);
			resultMap.put("Number", PushPayableNumber);
			return resultMap;
		};	
		
		ServiceLogBean logBean = new ServiceLogBean("FYLFKAction", "ecustom.finance.actions.CLBXAction-费用类付款-下推应付单",  "K3Cloud", "", System.currentTimeMillis());
		String yfdh = FinanceBean.getERPYfdh(super.getMainStringCK(mainFields, "yfdh", "下推应付单时，应付单号不能为空！"));
		String[] billNumber = new String[] {yfdh};	// 应付单号
		Map<String, Object> paramsMap = new HashMap<String, Object>();
		paramsMap.put("Ids", "");
		paramsMap.put("Numbers", billNumber);
		paramsMap.put("EntryIds", "");
		paramsMap.put("RuleId", "AP_HookPayableToFinPayableExp");
		paramsMap.put("TargetBillTypeId", "");
		paramsMap.put("TargetOrgId", 0);
		paramsMap.put("TargetFormId", "");
		paramsMap.put("IsEnableDefaultRule", "false");
		paramsMap.put("IsDraftWhenSaveFail", "false");
		paramsMap.put("CustomParams", null);
		Map<String, Object> erpResult = K3WebApiClient.pushData(logBean, paramsMap);
		Integer requestId = requestInfo.getRequestManager().getRequestid();
		int formId = requestInfo.getRequestManager().getFormid();
		int i =  updatePushTable(formId, requestId, erpResult);
		if(i > 0) {
			return erpResult;
		}else {
			throw new RuntimeException("修改推送费用应付单返回的信息失败！请联系管理员！");
		}
	}
	
	/**
	 * 
	 * @param requestInfo
	 * @param mainFields
	 * @return
	 * @throws Exception
	 * @throws Exception
	 */
	public ERPPPayableReq updatePushPayable(RequestInfo requestInfo, Property[] mainFields, Map<String, Object> payableMap) throws Exception, Exception {
		String fqzz = FinanceBean.getERPOrgNumber(super.getMainStringCK(mainFields, "fqzz", "发起组织不能为空！"));	// 所属公司
		String erpOrgNumber = super.getMainStringCK(mainFields, "ERPORGNUMBER", "ERP使用组织编码不能为空！");	// ERP使用组织编码
		String gys = FinanceBean.getERPGys(super.getMainStringCK(mainFields, "gys", "供应商不能为空！"), erpOrgNumber);	// 供应商
		String bb = super.getMainStringCK(mainFields, "bb", "币别不能为空！");	// 币别
		String lzlx = super.getMainStringCK(mainFields, "lzlx", "立账类型不能为空！");	// 立账类型
		String cgbm = FinanceBean.getERPDeptNumberV2(super.getMainString(mainFields, "cgbm"));	// 采购部门
		String fyzy = super.getMainString(mainFields, "fyzy");	// 费用摘要
		
		ERPPPayableReq repPUR = new ERPPPayableReq();
		repPUR.setIsAutoSubmitAndAudit("true");	// 审核
		repPUR.setIsDeleteEntry(false);
		repPUR.getModel().setFID(CustomUtil.getInteger(payableMap.get("FID")));	// 实体主键，有实体主键为修改操作，没有则新建
		repPUR.getModel().setFBiIINo(CustomUtil.getString(payableMap.get("Number")));	// 实体主键，有实体主键为修改操作，没有则新建
		repPUR.getModel().getFBillTypeID().put("FNUMBER", "YFD02_SYS");	// 固定值
		repPUR.getModel().setFBUSINESSTYPE("FY");
		repPUR.getModel().setFDATE(CustomUtil.getStringDate());	// 单据时间
		repPUR.getModel().setFENDDATE_H(CustomUtil.getStringDate());	// 到期日
		repPUR.getModel().getFSUPPLIERID().put("FNumber", gys);	// 供应商
		repPUR.getModel().getFCURRENCYID().put("FNumber", bb);	// 币别
		repPUR.getModel().setFISPRICEEXCLUDETAX(true);	// 价外税
		repPUR.getModel().setFISTAX(true);	// 按含税单价录入
		repPUR.getModel().getFSETTLEORGID().put("FNumber", fqzz);	// 结算组织
		repPUR.getModel().getFPAYORGID().put("FNumber", fqzz);	// 付款组织
		repPUR.getModel().setFSetAccountType(lzlx);	//  立账类型：固定财务应付
		repPUR.getModel().setFAP_Remark(FinanceBean.delHTMLTag(FinanceBean.subRemark(fyzy)));	// 备注- 费用摘要
		if(CustomUtil.isNotBlank(cgbm)) {
			repPUR.getModel().getFPURCHASEDEPTID().put("FNumber", cgbm);	// 采购部门
		}
		repPUR.getModel().setFCancelStatus("A");	// 作废状态，默认：A
		repPUR.getModel().setF_SZXY_OARequestID(requestInfo.getRequestManager().getRequestid()+"");	// OAID
		repPUR.getModel().setFsubHeadSuppiler(getFsubHeadSuppiler(gys));	// 表头供应商
		repPUR.getModel().setFsubHeadFinc(getFsubHeadFinc(mainFields));	// 表头财务
		
		// 明细表
		repPUR.getModel().setFEntityDetail(getFEntityDetail(requestInfo, mainFields, payableMap));
		return repPUR;
	}
	
	/**
	 * 
	 * @param requestInfo
	 * @param mainFields
	 * @return
	 * @throws Exception
	 * @throws Exception
	 */
	public List<FEntityDetail> getFEntityDetail(RequestInfo requestInfo, Property[] mainFields, Map<String, Object> payableMap) throws Exception, Exception {
		Integer requestid = requestInfo.getRequestManager().getRequestid();
		int formid = requestInfo.getRequestManager().getFormid();
		Map<String, Object> maxAmountMap = FinanceBean.getFYLFKMaxAmount(formid, "DT1", requestid);	// 查询当前单据最大金额
		String rowId = CustomUtil.getString(maxAmountMap.get("ID"));
		String pushPayableNumber =  CustomUtil.getString(payableMap.get("Number"));;	// 下推应付单编码
		Map<Integer, CustomMap> erpDetailMap = FinanceBean.getERPDetailData(pushPayableNumber);
		
		DetailTable  detailTable = requestInfo.getDetailTableInfo().getDetailTable(0);
		List<FEntityDetail> listFEntity = new ArrayList<FEntityDetail>();
		for(Row row: detailTable.getRow()) {
			String cplb = super.getCellString(row, "cplb");	// 产品类别ID
			Double bhsje = super.getCellDoubleValue(row, "bhsje");	// 不含税金额
			Double se = super.getCellDoubleValue(row, "se");	// 税额
			
			String fyxm = super.getCellString(row, "fyxmbm");	// 费用项目ID
			String fycdbm = super.getCellString(row, "fycdbm");	// 费用承担部门ID
			Double jshj = super.getCellDoubleValue(row, "jshj");	// 价税合计
			String rkqj = super.getCellString(row, "rkqj");	// 费用内容(费用类必须填写)
			String yfsm_new = super.getCellString(row, "yfsm_new");	//运费说明
			
			// 费用项目+费用承担部门+运费说明编码=查询ERP明细ID
			Integer erpmxnm = FinanceBean.getERPDetailId(pushPayableNumber, fyxm, fycdbm, yfsm_new);
			log.debug("erpmxnm；"+erpmxnm);
			// 处理
			if(erpDetailMap.containsKey(erpmxnm)) {	// 包含的情况做删除
				erpDetailMap.remove(erpmxnm);
			}
			
			FEntityDetail detail = new FEntityDetail();
			detail.setFEntryID(erpmxnm);	// 传输修改ERP明细数据
			detail.getFCOSTID().put("FNumber", FinanceBean.getERPFyxm(fyxm));	// 费用项目编码
			detail.getFCOSTDEPARTMENTID().put("FNUMBER", FinanceBean.getERPDeptNumberV2(fycdbm));	// 费用承担部门
			if(CustomUtil.isNotBlank(yfsm_new)) {
				detail.getF_SZXY_FREIGHTNOTE().put("FNumber", yfsm_new);	// 运费说明
			}
			if(CustomUtil.isNotBlank(erpmxnm)) {	// 若关联ERP的明细内码ID为空的情况，已完全到票 = false
				detail.setFISINVOICEALLARRIVED("true");	// 已完全到票
			}else {
				detail.setFISINVOICEALLARRIVED("false");	// 已完全到票
			}
			detail.setFComment(FinanceBean.subRemark(rkqj)); 	// 费用内容(费用类必须填写)
			
			// 发票费用明细
			if(CustomUtil.isNotBlank(rowId) && rowId.equals(row.getId())) {
				List<FEntityDetail> invoiceDetail = handlInvoiceDetail(requestInfo, detail);
				if(invoiceDetail.size() > 0) {
					// 若涉及发票的情况下，税额（传进项税的总和）字段在发票方法里面处理
					detail.setFNoTaxAmountFor_D(jshj-detail.getFTAXAMOUNTFOR_D());	// 不含税金额=价税合计-发票汇总进项税税额
					detail.setFALLAMOUNTFOR_D(jshj-detail.getFTAXAMOUNTFOR_D());	// 价税合计= 价税合计-发票汇总进项税税额
					detail.setFTAXAMOUNTFOR_D(0.0);	// 税额
				}else {
					// 若不涉及发票的情况下，原值不变
					detail.setFTAXAMOUNTFOR_D(0.0);	// 税额
					detail.setFNoTaxAmountFor_D(jshj);	// 不含税金额
					detail.setFALLAMOUNTFOR_D(jshj);	// 价税合计
				}
				
				listFEntity.add(detail);
				listFEntity.addAll(invoiceDetail);	// 将发票费用明细写入到ERP里面
			}else {
				detail.setFNoTaxAmountFor_D(jshj);	// 不含税金额
				detail.setFTAXAMOUNTFOR_D(0.0);	// 税额
				detail.setFALLAMOUNTFOR_D(jshj);	// 价税合计
				listFEntity.add(detail);
			}
			
		}
		
		// 处理金额为0的明细数据
		setDeleteData(listFEntity, erpDetailMap);
		
		return listFEntity;
	}
	
	/**
	 *  赋值原应付单的数据
	 * @param listFEntity
	 * @param erpDetailMap
	 */
	public void setDeleteData(List<FEntityDetail> listFEntity, Map<Integer, CustomMap> erpDetailMap) {
		log.info("赋值金额为0的明细数据-erpDetailMap:"+JsonUtil.toJson(erpDetailMap));
		for(Map.Entry<Integer, CustomMap> entry : erpDetailMap.entrySet()) {
			Integer key = entry.getKey();  
			CustomMap erpData = entry.getValue(); 
			FEntityDetail detail = new FEntityDetail();
			detail.setFEntryID(key);	// 传输修改ERP明细数据
			detail.getFCOSTID().put("FNumber", erpData.getString("FEXPNUMBER"));	// 费用项目编码
			detail.getFCOSTDEPARTMENTID().put("FNUMBER", erpData.getString("FDEPTNUMBER"));	// 费用承担部门
			detail.setF_SZXY_Text1("");	// 备注发票号
			detail.setFTAXAMOUNTFOR_D(0.0);	// 税额
			detail.setFNoTaxAmountFor_D(0.0);	// 不含税金额
			detail.setFALLAMOUNTFOR_D(0.0);	// 价税合计
			detail.setFISINVOICEALLARRIVED("true");	// 已完全到票
			if(CustomUtil.isNotBlank(erpData.getString("F_SZXY_FREIGHTNOTE"))) {
				detail.getF_SZXY_FREIGHTNOTE().put("FNumber", erpData.getString("F_SZXY_FREIGHTNOTE"));	// 运费说明
			}
			listFEntity.add(detail);
		}
	}
	
	
	/**
	 * 表头供应商
	 * @param requestInfo
	 * @param supplierNumber	供应商编码
	 * @return
	 */
	private FsubHeadSuppiler getFsubHeadSuppiler(String supplierNumber) {
		FsubHeadSuppiler fhs = new FsubHeadSuppiler();
		fhs.getFTRANSFERID().put("FNumber", supplierNumber);
		fhs.getFChargeId().put("FNumber", supplierNumber);
		fhs.getFORDERID().put("FNumber", supplierNumber);
		return fhs;
	}
	
	/**
	 * 表头财务
	 * @param requestInfo
	 * @param mainFields
	 * @return
	 */
	private FsubHeadFinc getFsubHeadFinc(Property[] mainFields) {
		String bb = super.getMainStringCK(mainFields, "bb", "币别不能为空！");	// 币别
		Double hl = super.getMainDouble(mainFields, "hl");	// 汇率
		FsubHeadFinc fhf = new FsubHeadFinc();
		fhf.getFMAINBOOKSTDCURRID().put("FNumber", "PRE001");	//  本位币，固定人民币
		if(!"PRE001".equals(bb)) {
			fhf.setFExchangeRate(hl);	// 汇率
		}
		fhf.getFEXCHANGETYPE().put("FNumber", "HLTX01_SYS");	// 汇率类型，固定值：HLTX01_SYS
		fhf.setFACCNTTIMEJUDGETIME(CustomUtil.getStringDate());	// 到期日计算日期
		return fhf;
	}
	
	/**
	 * 处理发票费用明细
	 * @param invoiceNumbers
	 * @param entry
	 * @param taxSum
	 * @return
	 * @throws Exception
	 */
	private List<FEntityDetail> handlInvoiceDetail(RequestInfo requestInfo, FEntityDetail detail) throws Exception {
		Double taxSum = 0.0;
		DetailTable  detailTable = requestInfo.getDetailTableInfo().getDetailTable(1);
		List<FEntityDetail> invoiceDetail = new ArrayList<FEntityDetail>();
		for(Row row: detailTable.getRow()) {
			String invoiceNumbers = super.getCellString(row, "fphm");
			List<CustomMap> invoiceMap = FinanceBean.getInvoiceData(invoiceNumbers);	// 发票号码
			if(CustomUtil.isNotBlank(invoiceMap)) {
				for(CustomMap map : invoiceMap) {
					Double tax = map.getDouble("DTAX");
					if(CustomUtil.isNotBlank(tax) && tax > 0) {
						FEntityDetail newDetail = new FEntityDetail();
						newDetail.getFCOSTID().put("FNumber", detail.getFCOSTID().get("FNumber"));	// 费用项目编码
						newDetail.getFCOSTDEPARTMENTID().put("FNUMBER", detail.getFCOSTDEPARTMENTID().get("FNUMBER"));	// 费用承担部门
						newDetail.setF_SZXY_Text1(map.getString("INVOICENUMBER"));	// 备注发票号
						if(CustomUtil.isNotBlank(detail.getF_SZXY_FREIGHTNOTE().get("FNumber"))) {
							newDetail.getF_SZXY_FREIGHTNOTE().put("FNumber", detail.getF_SZXY_FREIGHTNOTE().get("FNumber"));	// 运费说明
						}
						// 2023-10-31新增接口字段和逻辑
						String type = map.getString("INVOICETYPE");	// 进项税类型：0：税一；1：税二
						log.info("进项税类型："+type);
						if("2".equals(type) ||  "20".equals(type) ||  "21".equals(type) || "32".equals(type) ) {	// 为专票的进项税类型：0：税一；1：税二
							newDetail.setF_SZXY_INPUTTAXTYPE(0);
						}else {
							newDetail.setF_SZXY_INPUTTAXTYPE(1);	// 税二
						}
						newDetail.setFComment(FinanceBean.subRemark(detail.getFComment()));	// 费用内容(费用类必须填写)
						newDetail.setFNoTaxAmountFor_D(null);	// 不含税金额
						newDetail.setFTAXAMOUNTFOR_D(tax);	// 税额
						newDetail.setFALLAMOUNTFOR_D(tax);	// 价税合计
						newDetail.setFISINVOICEALLARRIVED("false");	// 已完全到票
						invoiceDetail.add(newDetail);
						taxSum = CustomUtil.add(taxSum, tax);	// 进项税累加
					}
					
				}
			}
		}
		
		detail.setFTAXAMOUNTFOR_D(taxSum);	// 赋值发票的可抵扣税额
		return invoiceDetail;
	}
	
	private int updatePushTable(Integer formId, Integer requestId, Map<String, Object> erpResult) throws SQLException {
		Integer erpFID = CustomUtil.getInteger(erpResult.get("FID"));
		String erpNumber = CustomUtil.getString(erpResult.get("Number"));
		String tableName = "FORMTABLE_MAIN_" + Math.abs(formId);
		String updateSql = "UPDATE "+tableName+" SET PushPayableFID=?, PushPayableNumber=? WHERE REQUESTID=?";
		int i = DB.conn().executeUpdate(updateSql, erpFID, erpNumber, requestId);
		return i;
	}

}
